﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace HOOMT
{
    public partial class ObjectModelForm : OriginalModelForm
    {
        #region 属性
        //parentOrderObjectDiagram不需要存数据库
        public HighOrderObjectDiagram parentOrderObjectDiagram = null;
        #endregion
        //####################################################################################
        #region 构造函数
        public ObjectModelForm(MainForm m)
        {
            parentMainForm = m;//获取父窗口的引用
            SystemVar.ShowToolStrip(this);
            //使菜单项无效
            //formMenuStrip.Items[0].Enabled = false;
            //添加新的菜单项
            ToolStripMenuItem tool2 = new ToolStripMenuItem();
            tool2.Name = "tool2";
            tool2.Text = "bbb";
            formMenuStrip.Items.Add(tool2);
            //隐藏菜单
            //formMenuStrip.Items[2].Visible = false;
        }
        #endregion

        #region 窗口属性改变函数集
        //************************************************************************************
        protected override void ModelForm_Click(object sender, EventArgs e)
        {
            this.BringToFront();
            this.Focus();
            SystemVar.ShowToolStrip(this);
        }
        //************************************************************************************
        protected override void ModelForm_FormClosing(object sender, FormClosingEventArgs e)
        {
            parentMainForm.splitContainer3.Panel1.Controls.Remove(parentMainForm.objectModelToolStrip);
            e.Cancel = true;
            base.OnClosing(e);
            this.Hide();
        }
        //************************************************************************************
        protected override void ModelForm_Resize(object sender, EventArgs e)
        {
            if (this.WindowState != FormWindowState.Minimized)
            {
                this.BringToFront();
                this.Focus();
                parentMainForm.currentDiagramFlag = Diagram.NullObject;//图形对象标志复位为空
                SystemVar.ShowToolStrip(this);
            }
            else
            {
                parentMainForm.splitContainer3.Panel1.Controls.Remove(parentMainForm.objectModelToolStrip);
            }
        }
        //************************************************************************************
        //重写WinProc函数拦截消息，处理窗体标题栏点击事件
        protected override void WndProc(ref Message m)
        {
            if (m.Msg == 0xa1 && (int)m.WParam == 0x2)
            {
                SystemVar.ShowToolStrip(this);
            }
            base.WndProc(ref m);
        }
        #endregion

        #region 图形对象鼠标响应函数集
        //************************************************************************************
        protected override void ModelForm_MouseEnter(object sender, EventArgs e)
        {
            //if (this.Focused)
            {
                switch (parentMainForm.currentDiagramFlag)
                {
                    case Diagram.HighOrderObject:
                        Cursor = System.Windows.Forms.Cursors.Cross;
                        break;
                    case Diagram.PrimitiveObject:
                        Cursor = System.Windows.Forms.Cursors.Cross;
                        break;
                    case Diagram.SimpleRelationship:
                        Cursor = System.Windows.Forms.Cursors.UpArrow;
                        break;
                    case Diagram.ComplexRelationship:
                        Cursor = System.Windows.Forms.Cursors.UpArrow;
                        break;
                    case Diagram.NullObject:
                        Cursor = System.Windows.Forms.Cursors.Default;
                        break;
                }
            }
        }
        //************************************************************************************
        protected override void ModelForm_MouseDown(object sender, MouseEventArgs e)
        {
            #region 左键双击
            if (e.Clicks == 2 && e.Button == MouseButtons.Left)
            {
                #region 双击弹出对话框
                //双击弹出对话框或进入下层设计
                foreach (OriginalDiagram diag in diagramList)
                {
                    //当图形对象为HighOrderObjectDiagram类的对象
                    if (diag is HighOrderObjectDiagram)
                    {
                        HighOrderObjectDiagram obj = (HighOrderObjectDiagram)diag;
                        Rectangle rect = new Rectangle(diag.UpLeftpoint.X, diag.UpLeftpoint.Y, diag.Width / 2, diag.Height);
                        Rectangle rect1 = new Rectangle(diag.UpLeftpoint.X + diag.Width / 2, diag.UpLeftpoint.Y + 2 * diag.Height / 21, diag.Width / 2, 5 * diag.Height / 21);
                        Rectangle rect2 = new Rectangle(diag.UpLeftpoint.X + diag.Width / 2, diag.UpLeftpoint.Y + 8 * diag.Height / 21, diag.Width / 2, 5 * diag.Height / 21);
                        Rectangle rect3 = new Rectangle(diag.UpLeftpoint.X + diag.Width / 2, diag.UpLeftpoint.Y + 14 * diag.Height / 21, diag.Width / 2, 5 * diag.Height / 21);
                        Point pt = new Point(e.X, e.Y);
                        //处理显示平台
                        if (rect.Contains(pt))
                        {
                            //图形对象当前没有下层分解平台，构造新MainForm，以无模式对话框形式弹出
                            if (!obj.HasModelForm)
                            {
                                ObjectModelForm modelForm = new ObjectModelForm(parentMainForm);//
                                modelForm.Text = "ObjectModelForm/ " + obj.Name;//图形对象名字与其包含的MainForm名字一致//

                                parentMainForm.modelFormList.Add(modelForm);//添加Form对象到MainForm的对象列表modelFormList
                                //parentMainForm.diagramList_List.Add(modelForm.diagramList);//添加Form对象的对象链表到MainForm的对象列表diagramList_List
                                modelForm.TopLevel = false;
                                parentMainForm.splitContainer3.Panel2.Controls.Add(modelForm);
                                //modelForm.preTreeNode = obj.treeNode;
                                //增加相应树节点
                                //TreeNode node = new TreeNode("Main");
                                //node.ContextMenuStrip = parentMainForm.formMenuStrip;//增加响应菜单（右击）
                                //node.Tag = modelForm;//节点指向绘制载体
                                //obj.treeNode.Nodes.Add(node);
                                //modelForm.preTreeNode = this.preTreeNode.Nodes[obj.highDiagramNum + 1];//更新Form的preTreeNode
                                //modelForm.preTreeNode.Nodes.Add("Main");//增加Form
                                //modelForm.formNodeFullPath = obj.diagramNodeFullPath + "\\Main";//fullPath,用于删除对象
                                //modelForm.preTreeNode.Nodes[1].ContextMenuStrip = parentMainForm.formMenuStrip;//增加响应菜单（右击）

                                obj.NewModelForm = modelForm;
                                obj.HasModelForm = true;

                                //新建的Form属于obj对象
                                modelForm.parentOrderObjectDiagram = obj;
                                //添加外部接口对象
                                addExternalInterface(obj, modelForm);

                                modelForm.BringToFront();
                                modelForm.Show();
                                modelForm.Focus();
                            }
                            //图形对象当前有下层分解平台，原有的非模式窗口获得焦点
                            else
                            {
                                obj.NewModelForm.BringToFront();
                                obj.NewModelForm.Show();
                                obj.NewModelForm.Focus();
                            }
                            break;
                        }
                        //处理方法
                        else
                        {
                            //根据双击坐标弹出对话框
                            if (rect1.Contains(pt))
                            {
                                showSpecificationDialogandUpdataDiagramContent(obj, "attributesTabControl");
                                break;
                            }
                            else if (rect2.Contains(pt))
                            {
                                showSpecificationDialogandUpdataDiagramContent(obj, "methodsTabControl");
                                break;
                            }
                            else if (rect3.Contains(pt))
                            {
                                showSpecificationDialogandUpdataDiagramContent(obj, "NFRTabControl");
                                break;
                            }
                            //更新图形对象数据
                        } 
                    }
                    //当图形对象为PrimitiveObjectDiagram类的对象
                    else if (diag is PrimitiveObjectDiagram)
                    {
                        PrimitiveObjectDiagram obj = (PrimitiveObjectDiagram)diag;
                        Rectangle rect1 = new Rectangle(diag.UpLeftpoint.X, diag.UpLeftpoint.Y, diag.Width, diag.Height / 3);
                        Rectangle rect2 = new Rectangle(diag.UpLeftpoint.X, diag.UpLeftpoint.Y + diag.Height / 3, diag.Width, diag.Height / 3);
                        Rectangle rect3 = new Rectangle(diag.UpLeftpoint.X, diag.UpLeftpoint.Y + 2 * diag.Height / 3, diag.Width, diag.Height / 3);
                        Point pt = new Point(e.X, e.Y);
                        
                        if (rect1.Contains(pt))
                        {
                            showSpecificationDialogandUpdataDiagramContent(obj, "attributesTabControl");
                            break;
                        }
                        else if (rect2.Contains(pt))
                        {

                            showSpecificationDialogandUpdataDiagramContent(obj, "methodsTabControl");
                            break;
                        }
                        else if (rect3.Contains(pt))
                        {
                            showSpecificationDialogandUpdataDiagramContent(obj, "NFRTabControl");
                            break;
                        }
                    }
                }
                #endregion
            }
            #endregion

            #region 鼠标左击
            else if(/*e.Button == MouseButtons.Left*/true)
            {
                ClearSelection();
                Point pt = new Point(e.X, e.Y);
                //添加图形对象
                if ((parentMainForm.currentDiagramFlag == Diagram.HighOrderObject || parentMainForm.currentDiagramFlag == Diagram.PrimitiveObject))
                {
                    AddDiagram(parentMainForm.currentDiagramFlag, pt);
                }
                //画线准备
                else if ((parentMainForm.currentDiagramFlag == Diagram.SimpleRelationship || parentMainForm.currentDiagramFlag == Diagram.ComplexRelationship))
                {
                    DrawingLinePre(pt);
                }
                //选中操作
                else if (parentMainForm.currentDiagramFlag == Diagram.NullObject)
                {
                    SelectDiagram(pt);
                    SelecteLine(pt);
                }
                //缩放准备
                if (preSelectedDiagram != null)
                {
                    selectedMagnifyingDiagramPoint(pt);
                }
            }
            #endregion

            #region 鼠标右击
            if (e.Button == MouseButtons.Right)
            {
                ShowContextMenuStrip(new Point(e.X, e.Y));
            }
            #endregion

            #region 文字同步
            //使所有对象的NameBox失去焦点
            parentMainForm.objectModelToolStrip.Focus();
            RenameProcess();
            #endregion
        }
        //************************************************************************************
        protected override void ModelForm_MouseMove(object sender, MouseEventArgs e)
        {
            //移动
            Point pt = new Point(e.X, e.Y);
            if (selectedDiagram != null && movingDiagramFlag)
            {
                MovingDiagram(selectedDiagram, pt);
            }
            //缩放
            else if (preSelectedDiagram != null && magnifyingDiagramFlag)
            {
                magnifyingDiagram(pt);
            }
            //画线
            else if (lineStartDiagram != null && drawingLineFlag)
            {
                DrawingLine(pt);
            }
        }
        //************************************************************************************
        protected override void ModelForm_MouseUp(object sender, MouseEventArgs e)
        {
            Point pt = new Point(e.X, e.Y);
            //移动
            if (selectedDiagram != null && movingDiagramFlag)
            {
                MovedDiagram(selectedDiagram, pt);
            }
            //缩放
            else if (preSelectedDiagram != null && magnifyingDiagramFlag)
            {
                magnifiedDiagram(pt);
            }
            //画线
            else if (lineStartDiagram != null && drawingLineFlag)
            {
                DrawedLine(parentMainForm.currentDiagramFlag, pt);
            }
            base.ModelForm_MouseUp(sender, e);
        }
        #endregion
        //
        private void showSpecificationDialogandUpdataDiagramContent(ObjectDiagram obj,string tabDialog)
        {
            ObjectSpecificationDialog objectSpecification = initSpecificationDialog(obj);
            objectSpecification.setShowTabControl(tabDialog);
            if (objectSpecification.ShowDialog() == DialogResult.OK)
            {
                updataDiagramContent(obj, objectSpecification);
            }
            Invalidate();
        }
        //
        private  ObjectSpecificationDialog initSpecificationDialog(ObjectDiagram obj)
        {
            //初始化对话框
            ObjectSpecificationDialog objectSpecification = new ObjectSpecificationDialog();
            objectSpecification.ObjectName = obj.Name;
            objectSpecification.Type = obj.Type;
            objectSpecification.StereoType = obj.Stereotype;
            objectSpecification.ExportControl = obj.ExportControl;
            objectSpecification.Documentation = obj.Documengtation;
            if (this.parentOrderObjectDiagram == null)
            {
                //查找此form对应的HighOrderObjectDiagram
                foreach (OriginalModelForm modelForm in this.parentMainForm.modelFormList)
                {
                    foreach(OriginalDiagram diagram in modelForm.diagramList)
                    {
                        if (diagram is HighOrderObjectDiagram && ((HighOrderObjectDiagram)diagram).newModelFormId == this.id)//相与短路
                        {
                            this.parentOrderObjectDiagram = (HighOrderObjectDiagram)diagram;
                            break;//如何跳出两层循环？？？
                        }
                    }
                }
            }
            objectSpecification.ParentOrderObjectDiagram = this.parentOrderObjectDiagram;
            //填充NFR窗口内容
            StringBuilder NFRBuilder = new StringBuilder();//NFR
            if (obj.ObjectNFRList.Count != 0)
            {
                foreach (NonFunctionRequirment requirment in obj.ObjectNFRList)
                {
                    objectSpecification.TemporaryObjectNFRList.Add(requirment);
                }
                if (obj.ObjectNFRList.Count != 0)
                {
                    NFRBuilder.AppendLine(obj.Name + "=[" + getNFRListString(obj.ObjectNFRList) + "]");//NFR
                }
            }
            //填充methods窗口内容
            StringBuilder methodsBuilder = new StringBuilder();
            foreach (Method method in obj.MethodList)
            {
                methodsBuilder.AppendLine(method.ToString());
                objectSpecification.TemporaryMethodList.Add(method);//临时列表同步对象方法列表
                if (method.MethodNFRList.Count != 0)
                {
                    NFRBuilder.AppendLine(method.MethodName + "=[" + getNFRListString(method.MethodNFRList) + "]");//NFR
                }
            }
            //更新方法对话框显示
            objectSpecification.MethodShowBox.Text = methodsBuilder.ToString();

            //填充attributes窗口内容
            StringBuilder attributesBuilder = new StringBuilder();
            foreach (Attribute attr in obj.AttributeList)
            {
                attributesBuilder.AppendLine(attr.ToString());
                objectSpecification.TemporaryAttributeList.Add(attr);
                if (attr.AttributeNFRList.Count != 0)
                {
                    NFRBuilder.AppendLine(attr.AttributeName + "=[" + getNFRListString(attr.AttributeNFRList) + "]");//NFR
                }
            }
            objectSpecification.AttributeShowBox.Text = attributesBuilder.ToString();

            objectSpecification.NonFunctionShowBox.Text = NFRBuilder.ToString();//NFR
            //填充Relations窗口内容
            {
                StringBuilder relationBuilder = new StringBuilder();
                foreach (OriginalLine line in straightlineList)
                {
                    if (line.StartDiagram.Equals(obj))
                    {
                        relationBuilder.AppendLine(line.EndDiagram.Name);
                    }
                    else if (line.EndDiagram.Equals(obj))
                    {
                        relationBuilder.AppendLine(line.StartDiagram.Name);
                    }
                }
                objectSpecification.RelationsShowBox.Text = relationBuilder.ToString();
            }
            //
            return objectSpecification;
        }

        private string getNFRListString(List<NonFunctionRequirment> NFRList)
        {
            StringBuilder NFRBuilder = new StringBuilder();
            foreach (NonFunctionRequirment requirment in NFRList)
            {
                NFRBuilder.Append(requirment.ToString());
            }
            return NFRBuilder.ToString();
        }
        //
        private void updataDiagramContent(ObjectDiagram obj, ObjectSpecificationDialog objectSpecification)
        {
            obj.MethodList.Clear();//清空原有方法链表
            foreach (Method method in objectSpecification.TemporaryMethodList)
            {
                obj.MethodList.Add(method);//更新方法链表
            }
            //更新属性
            obj.AttributeList.Clear();
            foreach (Attribute attr in objectSpecification.TemporaryAttributeList)
            {
                obj.AttributeList.Add(attr);
            }
            //更新约束
            obj.ObjectNFRList.Clear();
            foreach (NonFunctionRequirment requirment in objectSpecification.TemporaryObjectNFRList)
            {
                obj.ObjectNFRList.Add(requirment);
            }
            //更新Detail
            obj.Name = objectSpecification.ObjectName;
            obj.NameBox.Text = obj.Name;
            obj.Type = objectSpecification.Type;
            obj.Stereotype = objectSpecification.StereoType;
            obj.ExportControl = objectSpecification.ExportControl;
            obj.Documengtation = objectSpecification.Documentation;
        }
        //
        private void addExternalInterface(HighOrderObjectDiagram obj, OriginalModelForm modelForm)
        {
            int externalInterfaceWidth = 30;
            foreach (OriginalLine line in straightlineList)
            {
                if (line.StartDiagram.Equals(obj))
                {
                    ExternalInterfaceOut outInterface = new ExternalInterfaceOut(line.EndDiagram.UpLeftpoint, externalInterfaceWidth, externalInterfaceWidth, line.EndDiagram.id);
                    outInterface.Name = "External Interface" + line.EndDiagram.Name;
                    outInterface.id = line.EndDiagram.id;
                    modelForm.diagramList.Add(outInterface);
                }
                else if (line.EndDiagram.Equals(obj))
                {
                    ExternalInterfaceIn inInterface = new ExternalInterfaceIn(line.StartDiagram.UpLeftpoint, externalInterfaceWidth, externalInterfaceWidth, line.StartDiagram.id);
                    inInterface.Name = "External Interface" + line.StartDiagram.Name;
                    inInterface.id = line.StartDiagram.id;
                    modelForm.diagramList.Add(inInterface);
                }
            }
        }
    }
}
  
 